package com.my.kindlesend.config;

import jakarta.validation.constraints.NotNull;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;

import java.util.concurrent.LinkedBlockingQueue;
import java.util.concurrent.ThreadFactory;
import java.util.concurrent.ThreadPoolExecutor;
import java.util.concurrent.TimeUnit;

/**
 * 线程池配置类
 * 配置用于文件发送任务的线程池
 */
@Configuration
public class ThreadPoolConfig {
    
    /**
     * 创建文件发送线程池
     * @return 配置好的ThreadPoolExecutor对象
     */
    @Bean(name = "fileSendThreadPool")
    public ThreadPoolExecutor fileSendThreadPool() {
        // 核心线程数：根据系统资源和业务需求设置
        int corePoolSize = 5;
        // 最大线程数：处理峰值负载时的最大线程数
        int maxPoolSize = 10;
        // 线程空闲时间：超过核心线程数的线程在空闲多长时间后会被回收
        long keepAliveTime = 60L;
        // 时间单位：秒
        TimeUnit unit = TimeUnit.SECONDS;
        // 工作队列：用于存储等待执行的任务
        LinkedBlockingQueue<Runnable> workQueue = new LinkedBlockingQueue<>(500);
        // 线程工厂：设置线程名称前缀，便于日志追踪
        ThreadFactory threadFactory = new ThreadFactory() {
            private int count = 0;
            
            @Override
            public Thread newThread(@NotNull Runnable r) {
                Thread thread = new Thread(r);
                thread.setName("file-send-thread-" + (++count));
                return thread;
            }
        };
        // 拒绝策略：当线程池和队列都满时的处理策略
        // CallerRunsPolicy表示由调用线程（提交任务的线程）直接执行任务
        ThreadPoolExecutor.CallerRunsPolicy handler = new ThreadPoolExecutor.CallerRunsPolicy();
        
        // 创建线程池
        ThreadPoolExecutor executor = new ThreadPoolExecutor(
                corePoolSize,
                maxPoolSize,
                keepAliveTime,
                unit,
                workQueue,
                threadFactory,
                handler
        );
        
        // 设置允许核心线程超时回收（可选）
        executor.allowCoreThreadTimeOut(true);
        
        return executor;
    }
}